import argparse
import pysam

def check_bam(bam_file):
    try:
        # 初始化统计计数器
        total_reads = 0
        unmapped_reads = 0
        empty_pairs_reads = 0
        missing_cigar_reads = 0
        missing_ref_start_reads = 0

        # 打开 BAM 文件
        bam = pysam.AlignmentFile(bam_file, "rb")
        
        # 遍历每条读取
        for read in bam:
            total_reads += 1
            
            # 检查是否未比对
            if read.is_unmapped:
                unmapped_reads += 1
                missing_ref_start_reads += 1  # 未比对的读取没有 reference_start
            
            # 检查 get_aligned_pairs() 的第二列是否全为空
            pairs = read.get_aligned_pairs()
            if not pairs or all(pair[1] is None for pair in pairs):
                empty_pairs_reads += 1
            
            # 检查 CIGAR 字符串
            if not read.cigarstring:
                missing_cigar_reads += 1
            
            # 检查 reference_start
            if not read.is_unmapped and read.reference_start is None:
                missing_ref_start_reads += 1
        
        bam.close()
        
        # 输出统计结果
        print("BAM File Check Summary")
        print(f"Total Reads: {total_reads}")
        print(f"Unmapped Reads: {unmapped_reads} ({unmapped_reads/total_reads*100:.2f}%)")
        print(f"Reads with Empty get_aligned_pairs() Second Column: {empty_pairs_reads} ({empty_pairs_reads/total_reads*100:.2f}%)")
        print(f"Reads Missing CIGAR String: {missing_cigar_reads} ({missing_cigar_reads/total_reads*100:.2f}%)")
        print(f"Reads Missing Reference Start: {missing_ref_start_reads} ({missing_ref_start_reads/total_reads*100:.2f}%)")
        
    except Exception as e:
        print(f"Error processing BAM file: {e}")

def main():
    # 设置命令行参数
    parser = argparse.ArgumentParser(description="Check BAM file and output summary statistics.")
    parser.add_argument("bam_file", help="Path to the input BAM file")
    args = parser.parse_args()
    
    # 检查 BAM 文件
    check_bam(args.bam_file)

if __name__ == "__main__":
    main()